package systems.rpgBuilder;

import java.util.LinkedList;
import java.util.List;

import org.jdom.Element;

import equipments.enumeration.EquipmentSlots;

public class Item {
  private String multiLangueName;
  private String tableName;
  private String tableField;
  private String[] tableFieldValue;
  //The type of the item (wood, chain, mail, leather ...)
  private LinkedList<Type> itemTypesList = new LinkedList<Type>();

  //Because, one items can regroup multiple group of items ...
  private LinkedList<Item> subItemsList = new LinkedList<Item>();

  //The FullName of the class use to instanciate the items
  private String className;

  //Slots
  private LinkedList<EquipmentSlots> slotsList = new LinkedList<EquipmentSlots>();

  public Item(Element item)
  {
    this.multiLangueName = item.getChildText("multiLangueName");
    this.tableName = item.getChildText("tableName");
    this.tableField = item.getChildText("tableField");
    this.tableFieldValue = item.getChildText("tableFieldValue").split(",");
    //System.out.print("Construction de l'item : "+multiLangueName+"\n");
    buildTypesAndSubItemsList(item);
  }

  @SuppressWarnings("unchecked")
  private void buildTypesAndSubItemsList(Element item)
  {
    List<Element> itemChild = item.getChildren();
    try
    {
      for(int i=0; i<4; i++)
        itemChild.remove(0);

      // Now we are dealling with the optionnals elements.
      //The first one is "classFullName"
      if(itemChild.get(0).getName().equalsIgnoreCase("classFullName"))
      {
        //If it's a "classFullName" tag, we create the types ... 
        setClassName(itemChild.get(0).getText());
        // ... and remove it from the list
        itemChild.remove(0);
      }

      // Next one is a couple : "slotsEnumName" & "slotsEnumValues"
      if(itemChild.get(0).getName().equalsIgnoreCase("slotsEnumName")
          && itemChild.get(1).getName().equalsIgnoreCase("slotsEnumValues"))
      {
        String name = itemChild.get(0).getText();
        String[] values = itemChild.get(1).getText().split(" ");
        itemChild.remove(0);
        itemChild.remove(0);
        //If it's a "slotsEnumName" tag, we get the Enum constant ... 
        EquipmentSlots[] slots = (EquipmentSlots[]) Class.forName(name).getEnumConstants();
        for(String value : values)
          for(EquipmentSlots slot : slots)
            if(slot.toString().equalsIgnoreCase(value))
            {
              this.slotsList.add(slot);
              continue;
            }
        //System.out.println(this.className+" Slots : "+ this.slotsList.size());
      }

      // According to the DTD, the "types" must be after the "classFullName"
      // Then if the next element is "types" we will create the different type
      // Else we will create the item list
      if(itemChild.get(0).getName().equalsIgnoreCase("types"))
      {
        //If it's a "types" tag, we create the types ... 
        buildTypesList(itemChild.get(0));
        // ... and remove it from the list
        itemChild.remove(0);
      }
      //For each item, we create it and put it in the subItem list
      for(Element subItem : itemChild)
      {
        Item tmpItem = new Item(subItem);
        if(tmpItem.getClassName() == null)
          tmpItem.setClassName(this.className);
        if(tmpItem.getItemTypesList().size() == 0)
          tmpItem.setItemTypesList(this.itemTypesList);
        if(tmpItem.getSlotsList().size() == 0)
          tmpItem.setSlotsList(this.slotsList);
        this.subItemsList.add(tmpItem);
      }
    }catch(Exception e){ 
    }
  }

  private void setSlotsList(LinkedList<EquipmentSlots> slotsList2) {
    //System.out.println("L'item "+this.multiLangueName+" contient maintenant "+slotsList2.size()+" slots");
    this.slotsList = slotsList2;
  }

  private void buildTypesList(Element types) {
    List<Element> typeList = types.getChildren();
    for(Element type : typeList)
      this.itemTypesList.add(new Type(type));
  }

  /**
   * @return the multiLangueName
   */
  public String getMultiLangueName() {
    return multiLangueName;
  }

  /**
   * @return the tableName
   */
  public String getTableName() {
    return tableName;
  }

  /**
   * @return the tableField
   */
  public String getTableField() {
    return tableField;
  }

  /**
   * @return the tableFieldValue
   */
  public String[] getTableFieldValues() {
    return tableFieldValue;
  }

  /**
   * @return the itemTypesList
   */
  public LinkedList<Type> getItemTypesList() {
    return itemTypesList;
  }

  /**
   * @return the subItemsList
   */
  public LinkedList<Item> getSubItemsList() {
    return subItemsList;
  }

  public void setClassName(String newClassName)
  {
    //System.out.println("Nouvelle classe : "+newClassName+" pour l'item "+this.multiLangueName);
    this.className = newClassName;
  }

  public void setItemTypesList(LinkedList<Type> linkedList)
  {
    this.itemTypesList = linkedList; 
  }

  public String getClassName()
  {
    return this.className;
  }
  public String toString()
  {
    return multiLangueName;
  }
  
  public LinkedList<EquipmentSlots> getSlotsList()
  {
    return this.slotsList;
  }
}
